"use strict";

var path = require('path');
var fs = require('fs');
var crypto = require('crypto');

var gutil = require('gulp-util');
var through = require('through2');

var PLUGIN_NAME = 'gulp-asset-rev';

var ASSET_REG = {
    "SCRIPT": /(<script[^>]+src=)['"]([^'"]+)["']/ig,
    "STYLESHEET": /(<link[^>]+href=)['"]([^'"]+)["']/ig,
    "IMAGE": /(<img[^>]+src=)['"]([^'"]+)["']/ig,
    "BACKGROUND": /(url\()(?!data:|about:)([^)]*)/ig
};

var createHash = function (file, len) {
    return crypto.createHash('md5').update(file).digest('hex').substr(0, len);
};

module.exports = function (options) {
    return through.obj(function (file, enc, cb) {

        options = options || {};

        if (file.isNull()) {
            this.push(file);
            return cb();
        }

        if (file.isStream()) {
            this.emit('error', new gutil.PluginError(PLUGIN_NAME, 'Streaming not supported'));
            return cb();
        }

        var content = file.contents.toString();

        var filePath = path.dirname(file.path);
        if(options.revPublicJs==1){
            if(filePath.endsWith('js\\common')){
                filePath = filePath.substr(0,filePath.length-16);
            }
        }
        if(options.revPublicCss==1){
            ASSET_REG.IMPORT = /(@import[^.css]+)['"]([^'"]+)["']/ig;
        }
        if(options.revHtml == 1){
            if(filePath.indexOf('entrobusChain\\views')!=-1){
                filePath = filePath.split('entrobusChain\\views')[0] + "entrobusChain";
                content = content.replace('<base id="base" href="/../entrobusChain/">',options.htmlBase)
            }
        }
        //全局变量处理(HTML文件版本号Version等)
        if(options.restVariable == 1){
            var k = /(var[^;]+;)/ig;
            content = content.replace(k, function (str, tag, src) {
                if(str.indexOf('viewVersion') != -1 && options.viewVersion){
                   return  'var viewVersion = ' + options.viewVersion + ";";
                }
                return str;
            })
        }

        for (var type in ASSET_REG) {
            if (type === "BACKGROUND" && !/\.(css|scss|less)$/.test(file.path)) {

            } else {
                content = content.replace(ASSET_REG[type], function (str, tag, src) {
                    src = src.replace(/(^['"]|['"]$)/g, '');
                    if (!/\.[^\.]+$/.test(src)) {
                        return str;
                    }

                    if (options.verStr) {
                        src += options.verStr;
                        return tag + '"' + src + '"';
                    }
                
                    // remote resource
                    if (/^https?:\/\//.test(src)) {
                        return str;
                    }
                    var assetPath = path.join(filePath, src);
                    if (src.indexOf('/') == 0) {
                        if (options.resolvePath && typeof options.resolvePath === "function") {
                            assetPath = options.resolvePath(src);
                        } else {
                            assetPath = (options.rootPath || "") + src;
                        }
                    }

                    if(assetPath.indexOf('.js?v=') > -1){
                        assetPath = assetPath.split('.js?v=')[0] + '.js';
                    }
                    if(assetPath.indexOf('.css?v=') > -1){
                        assetPath = assetPath.split('.css?v=')[0] + '.css';
                    }

                    if (fs.existsSync(assetPath)) {

                        var buf = fs.readFileSync(assetPath);

                        var md5 = createHash(buf, options.hashLen || 7);

                        var verStr = (options.verConnecter || "-") + md5;

                        // src = src.replace(verStr, '').replace(/(\.[^\.]+)$/, verStr + "$1");
                        if(src.indexOf('.js?v=') > -1){
                            src = src.split('.js?v=')[0] + '.js';
                        }
                        if(src.indexOf('.css?v=') > -1){
                            src = src.split('.css?v=')[0] + '.css';
                        }
                        src=src+"?v="+verStr;

                    } else {
                        return str;
                    }

                    return tag + '"' + src + '"';
                });
            }
        }

        file.contents = new Buffer(content);
        this.push(file);
        cb();
    });
};

